iT邦幫忙

2022 iThome 鐵人賽

DAY 13
0
Mobile Development

Android app 效能優化系列 第 13

Android 的記憶體效能優化

  • 分享至 

  • xImage
  •  

這篇開始要進入到 Android 在使用記憶體上的效能優化。在記憶體效能篇,我們將依序來介紹跟記憶體效能有關的議題:

  • Android 的記憶體管理
  • OOM (Out of memory)
  • Memory leak 記憶體洩漏
  • Application Context 與 Activity Context
  • WeakReference 弱引用
  • Coroutine 減少背景執行緒造成的 Memory leak
  • Profiler 分析記憶體使用狀況
  • Memory leak 檢測工具 Leakcanary

現在我們就從 Android 的記憶體管理來開始介紹。在 Android 系統中,當我們產生了一個物件,就會在 Heap 中配置一塊記憶體來處理,當一個物件不再使用時,就會進行GC (Garbage Collection )垃圾回收機制來將資源釋放。而當一個物件已經不再被使用,卻無法被回收時,我們稱為 Memory leak 記憶體洩漏。當 Memory leak 越來越多,就代表被占用無法回收的記憶體越多,最後就可能會造成 OOM(Out of memory),也就是記憶體不足。

限制 App 的記憶體使用

記憶體在任何環境都是非常寶貴的資源,在行動裝置上更是如此。在 Android 手機不是只有我們的 App 正在執行,還有其他的背景 App、桌面 App、系統服務等。為了維持手機可以正常的運作,Android 會限制每個 App 的記憶體使用。當 App 使用達到了上限,就可能會收到 OOM。

查看記憶體使用狀況

如果想知道目前記憶體的使用狀況,可以透過 ActivityManager.MemoryInfo()查看記憶體的狀況,也能直接使用MemoryInfo.lowMemory 來取得目前是否處於低記憶體資源狀況。

if (getAvailableMemory().lowMemory) {
    //是否處於低記憶體資源狀況
}

println("availableMemory:${getAvailableMemory().availMem}")
println("totalMemory:${getAvailableMemory().totalMem}")

private fun getAvailableMemory(): ActivityManager.MemoryInfo {
    val activityManager = getSystemService(Context.ACTIVITY_SERVICE) as ActivityManager
    return ActivityManager.MemoryInfo().also { memoryInfo ->
        activityManager.getMemoryInfo(memoryInfo)
    }
}

記憶體不足管理

當我們關閉一個 App (進到背景模式) 時,系統不會馬上把 App 從記憶體中移除,而是將其留在記憶體中,方便使用者可以快速切換回這些 App。當記憶體資源不足時,系統就會依照如下列表的順序來決定先終止哪些程序。

  1. 背景App:當 App 被關閉,不會馬上從記憶體被移除,而是進到背景模式。
  2. 上次使用的App:由於使用者更有可能回到這個背景App,所以被終止的順序會比背景App來得低。
  3. Home app:用來顯示你的首頁的App,如果終止就可能會看到桌布不見。
  4. Services:例如在背地裡同步雲端資訊的Service。
  5. 可察覺的App:非前景的App,但使用者還是可以與之操作或看到,例如撥放音樂
  6. 前景App:目前正在執行的App,可以發現Android先終止一些沒有正在用的。
  7. 持續性:手機的核心服務,例如Wifi。
  8. 系統:當系統用的記憶體也不足,可能就會重啟手機。
  9. Native:較低階的程序。

所以我們在「從背景處理優化效能」就有介紹,如何選擇正確的背景服務,因為這會影響在記憶體不足時,被終止的優先順序。

下一篇我們就從 OOM 來開始一步步針對記憶體使用來優化吧。


上一篇
檢測畫面的重複繪製
下一篇
Out of memory 記憶體不足
系列文
Android app 效能優化30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言